/*
 * Copyright 2013 The Netty Project
 *
 * The Netty Project licenses this file to you under the Apache License,
 * version 2.0 (the "License"); you may not use this file except in compliance
 * with the License. You may obtain a copy of the License at:
 *
 *   http://www.apache.org/licenses/LICENSE-2.0
 *
 * Unless required by applicable law or agreed to in writing, software
 * distributed under the License is distributed on an "AS IS" BASIS, WITHOUT
 * WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. See the
 * License for the specific language governing permissions and limitations
 * under the License.
 */

package io.netty.util;

import static io.netty.util.internal.MathUtil.safeFindNextPositivePowerOfTwo;
import static java.lang.Math.max;
import static java.lang.Math.min;

import java.lang.ref.WeakReference;
import java.util.Arrays;
import java.util.Map;
import java.util.WeakHashMap;
import java.util.concurrent.atomic.AtomicInteger;

import io.netty.util.concurrent.FastThreadLocal;
import io.netty.util.internal.ObjectPool;
import io.netty.util.internal.SystemPropertyUtil;
import io.netty.util.internal.logging.InternalLogger;
import io.netty.util.internal.logging.InternalLoggerFactory;

/**
 * Light-weight object pool based on a thread-local stack.
 *
 * @param <T> the type of the pooled object
 */
public abstract class Recycler<T> {

    private static final InternalLogger logger = InternalLoggerFactory.getInstance(Recycler.class);

    @SuppressWarnings("rawtypes")
    private static final Handle NOOP_HANDLE = new Handle() {
        @Override
        public void recycle(Object object) {
            // NOOP
        }
    };
    private static final AtomicInteger ID_GENERATOR = new AtomicInteger(Integer.MIN_VALUE);
    private static final int OWN_THREAD_ID = ID_GENERATOR.getAndIncrement();
    private static final int DEFAULT_INITIAL_MAX_CAPACITY_PER_THREAD = 4 * 1024; // Use 4k instances as default.
    private static final int DEFAULT_MAX_CAPACITY_PER_THREAD;
    private static final int INITIAL_CAPACITY;
    private static final int MAX_SHARED_CAPACITY_FACTOR;
    private static final int MAX_DELAYED_QUEUES_PER_THREAD;
    /**WeakOrderQueue维护了多个link，每个link可以放LINK_CAPACITY个handle
     * 
     */
    private static final int LINK_CAPACITY;
    private static final int RATIO;

    static {
        // In the future, we might have different maxCapacity for different object types.
        // e.g. io.netty.recycler.maxCapacity.writeTask
        //      io.netty.recycler.maxCapacity.outboundBuffer
        int maxCapacityPerThread = SystemPropertyUtil.getInt("io.netty.recycler.maxCapacityPerThread",
                SystemPropertyUtil.getInt("io.netty.recycler.maxCapacity", DEFAULT_INITIAL_MAX_CAPACITY_PER_THREAD));
        if (maxCapacityPerThread < 0) {
            maxCapacityPerThread = DEFAULT_INITIAL_MAX_CAPACITY_PER_THREAD;
        }

        DEFAULT_MAX_CAPACITY_PER_THREAD = maxCapacityPerThread;

        MAX_SHARED_CAPACITY_FACTOR = max(2,
                SystemPropertyUtil.getInt("io.netty.recycler.maxSharedCapacityFactor",
                        2));

        MAX_DELAYED_QUEUES_PER_THREAD = max(0,
                SystemPropertyUtil.getInt("io.netty.recycler.maxDelayedQueuesPerThread",
                        // We use the same value as default EventLoop number
                        NettyRuntime.availableProcessors() * 2));

        LINK_CAPACITY = safeFindNextPositivePowerOfTwo(
                max(SystemPropertyUtil.getInt("io.netty.recycler.linkCapacity", 16), 16));

        // By default we allow one push to a Recycler for each 8th try on handles that were never recycled before.
        // This should help to slowly increase the capacity of the recycler while not be too sensitive to allocation
        // bursts.
        RATIO = safeFindNextPositivePowerOfTwo(SystemPropertyUtil.getInt("io.netty.recycler.ratio", 8));

        if (logger.isDebugEnabled()) {
            if (DEFAULT_MAX_CAPACITY_PER_THREAD == 0) {
                logger.debug("-Dio.netty.recycler.maxCapacityPerThread: disabled");
                logger.debug("-Dio.netty.recycler.maxSharedCapacityFactor: disabled");
                logger.debug("-Dio.netty.recycler.linkCapacity: disabled");
                logger.debug("-Dio.netty.recycler.ratio: disabled");
            } else {
                logger.debug("-Dio.netty.recycler.maxCapacityPerThread: {}", DEFAULT_MAX_CAPACITY_PER_THREAD);
                logger.debug("-Dio.netty.recycler.maxSharedCapacityFactor: {}", MAX_SHARED_CAPACITY_FACTOR);
                logger.debug("-Dio.netty.recycler.linkCapacity: {}", LINK_CAPACITY);
                logger.debug("-Dio.netty.recycler.ratio: {}", RATIO);
            }
        }

        INITIAL_CAPACITY = min(DEFAULT_MAX_CAPACITY_PER_THREAD, 256);
    }

    /**代表Stack最多能缓存多少个对象，如果缓存0个，说明对象将一个都不会回收
     * 
     */
    private final int maxCapacityPerThread;
    private final int maxSharedCapacityFactor;
    private final int interval;
    private final int maxDelayedQueuesPerThread;

    private final FastThreadLocal<Stack<T>> threadLocal = new FastThreadLocal<Stack<T>>() {
        @Override
        protected Stack<T> initialValue() {
            return new Stack<T>(Recycler.this, Thread.currentThread(), maxCapacityPerThread, maxSharedCapacityFactor, interval, maxDelayedQueuesPerThread);
        }

        @Override
        protected void onRemoval(Stack<T> value) {
            // Let us remove the WeakOrderQueue from the WeakHashMap directly if its safe to remove some overhead
            if (value.threadRef.get() == Thread.currentThread()) {
               if (DELAYED_RECYCLED.isSet()) {
                   DELAYED_RECYCLED.get().remove(value);
               }
            }
        }
    };

    protected Recycler() {
        this(DEFAULT_MAX_CAPACITY_PER_THREAD);
    }

    protected Recycler(int maxCapacityPerThread) {
        this(maxCapacityPerThread, MAX_SHARED_CAPACITY_FACTOR);
    }

    protected Recycler(int maxCapacityPerThread, int maxSharedCapacityFactor) {
        this(maxCapacityPerThread, maxSharedCapacityFactor, RATIO, MAX_DELAYED_QUEUES_PER_THREAD);
    }

    protected Recycler(int maxCapacityPerThread, int maxSharedCapacityFactor, int ratio, int maxDelayedQueuesPerThread) {
        interval = safeFindNextPositivePowerOfTwo(ratio);
        if (maxCapacityPerThread <= 0) {
            this.maxCapacityPerThread = 0;
            this.maxSharedCapacityFactor = 1;
            this.maxDelayedQueuesPerThread = 0;
        } else {
            this.maxCapacityPerThread = maxCapacityPerThread;
            this.maxSharedCapacityFactor = max(1, maxSharedCapacityFactor);
            this.maxDelayedQueuesPerThread = max(0, maxDelayedQueuesPerThread);
        }
    }

    @SuppressWarnings("unchecked")
    public final T get() {
    	// 代表Stack最多能缓存多少个对象，如果缓存0个，说明对象将一个都不会回收
        if (maxCapacityPerThread == 0) {
            return newObject((Handle<T>) NOOP_HANDLE);
        }
        // 通过FastThreadLocal对象获取当前线程的Stack
        Stack<T> stack = threadLocal.get();
        // 获取到Stack之后，从Stack中pop出一个handle
        DefaultHandle<T> handle = stack.pop();
        if (handle == null) {
        	// 如果取出的handle为空，则说明当前回收站内没有任何对象，通常第一次执行到这里对象还没有回收，就会是null，这样就会通过newHandle创建一个handle，这个handle的value属性，通过重写的newObject方法进行赋值
        	handle = stack.newHandle();
            handle.value = newObject(handle);
        }
        return (T) handle.value;
    }

    /**
     * @deprecated use {@link Handle#recycle(Object)}.
     */
    @Deprecated
    public final boolean recycle(T o, Handle<T> handle) {
        if (handle == NOOP_HANDLE) {
            return false;
        }

        DefaultHandle<T> h = (DefaultHandle<T>) handle;
        if (h.stack.parent != this) {
            return false;
        }

        h.recycle(o);
        return true;
    }

    final int threadLocalCapacity() {
        return threadLocal.get().elements.length;
    }

    final int threadLocalSize() {
        return threadLocal.get().size;
    }

    protected abstract T newObject(Handle<T> handle);

    public interface Handle<T> extends ObjectPool.Handle<T>  { }

    private static final class DefaultHandle<T> implements Handle<T> {
        /**表示handle上次回收的id
         * 
         */
        int lastRecycledId;
        int recycleId;

        /**表示当前对象之前是否没有被回收过
         * 
         */
        boolean hasBeenRecycled;

        /**当前handle所属的Stack
         * 
         */
        Stack<?> stack;
        /**绑定回收的对象本身
         * 
         */
        Object value;

        DefaultHandle(Stack<?> stack) {
            this.stack = stack;
        }

        @Override
        public void recycle(Object object) {
        	// 如果对象不一致，则抛出异常
            if (object != value) {
                throw new IllegalArgumentException("object does not belong to handle");
            }

            Stack<?> stack = this.stack;
            if (lastRecycledId != recycleId || stack == null) {
                throw new IllegalStateException("recycled already");
            }

            stack.push(this);
        }
    }

    private static final FastThreadLocal<Map<Stack<?>, WeakOrderQueue>> DELAYED_RECYCLED = new FastThreadLocal<Map<Stack<?>, WeakOrderQueue>>() {
        @Override
        protected Map<Stack<?>, WeakOrderQueue> initialValue() {
            return new WeakHashMap<Stack<?>, WeakOrderQueue>();
        }
    };

    // a queue that makes only moderate guarantees about visibility: items are seen in the correct order,
    // but we aren't absolutely guaranteed to ever see anything at all, thereby keeping the queue cheap to maintain
    private static final class WeakOrderQueue extends WeakReference<Thread> {

        static final WeakOrderQueue DUMMY = new WeakOrderQueue();

        // Let Link extend AtomicInteger for intrinsics. The Link itself will be used as writerIndex.
        @SuppressWarnings("serial")
        static final class Link extends AtomicInteger {
            /**每次创建一个link，都会创建一个DefaultHandle类型的数组用于放handle对象，默认大小为16
             * 
             */
            final DefaultHandle<?>[] elements = new DefaultHandle[LINK_CAPACITY];

            /**当前的读取位置
             * 
             */
            int readIndex;
            /**next指向下一个link
             * 
             */
            Link next;
        }

        // Its important this does not hold any reference to either Stack or WeakOrderQueue.
        private static final class Head {
            private final AtomicInteger availableSharedCapacity;

            Link link;

            Head(AtomicInteger availableSharedCapacity) {
                this.availableSharedCapacity = availableSharedCapacity;
            }

            /**回收所有已使用的空间，并断开节点的链接，以防止GC裙带关系
             * <br/>Reclaim all used space and also unlink the nodes to prevent GC nepotism.
             */
            void reclaimAllSpaceAndUnlink() {
                Link head = link;
                link = null;
                int reclaimSpace = 0;
                while (head != null) {
                    reclaimSpace += LINK_CAPACITY;
                    Link next = head.next;
                    // Unlink to help GC and guard against GC nepotism.
                    head.next = null;
                    head = next;
                }
                if (reclaimSpace > 0) {
                    reclaimSpace(reclaimSpace);
                }
            }

            private void reclaimSpace(int space) {
            	// 将availableSharedCapacity加上16，表示WeakOrderQueue还可以继续插入link
                availableSharedCapacity.addAndGet(space);
            }

            void relink(Link link) {
                reclaimSpace(LINK_CAPACITY);
                this.link = link;
            }

            /**
             * Creates a new {@link} and returns it if we can reserve enough space for it, otherwise it
             * returns {@code null}.
             */
            Link newLink() {
                return reserveSpaceForLink(availableSharedCapacity) ? new Link() : null;
            }

            /**WeakOrderQueue维护了多个link，link之间通过链表进行连接，每个link可以放LINK_CAPACITY个handle。这里将availableSharedCapacity - 16，
             * <br/>其实就表示先分配16个空间在link里，下次回收时，如果这16个空间没有填满，则可以继续往里放。如果已经填满，则通过继续添加link的方式继续分配16个空间用于放handle
             * <br/>WeakOrderQueuehe1WeakOrderQueue之间也是通过链表进行关联的，见《WeakOrderQueue之间》
             * @param availableSharedCapacity
             * @return
             */
            static boolean reserveSpaceForLink(AtomicInteger availableSharedCapacity) {
                for (;;) {
                    int available = availableSharedCapacity.get();
                    if (available < LINK_CAPACITY) {
                        return false;
                    }
                    if (availableSharedCapacity.compareAndSet(available, available - LINK_CAPACITY)) {
                        return true;
                    }
                }
            }
        }

        // chain of data items
        /**head和tail都指向一个link对象，其实在WeakOrderQueue中维护了一个链表，head和tail分别代表头节点和尾节点，初始状态下，头节点和尾节点都指向同一个节点
         * 
         */
        private final Head head;
        private Link tail;
        // pointer to another queue of delayed items for the same stack
        private WeakOrderQueue next;
        /**WeakOrderQueue的id，WeakOrderQueue每次创建的时候，都会自增一个唯一的id
         * 
         */
        private final int id = ID_GENERATOR.getAndIncrement();
        private final int interval;
        private int handleRecycleCount;

        private WeakOrderQueue() {
            super(null);
            head = new Head(null);
            interval = 0;
        }

        private WeakOrderQueue(Stack<?> stack, Thread thread) {
            super(thread);
            tail = new Link();

            // Its important that we not store the Stack itself in the WeakOrderQueue as the Stack also is used in
            // the WeakHashMap as key. So just store the enclosed AtomicInteger which should allow to have the
            // Stack itself GCed.
            head = new Head(stack.availableSharedCapacity);
            head.link = tail;
            interval = stack.interval;
            handleRecycleCount = interval; // Start at interval so the first one will be recycled.
        }

        static WeakOrderQueue newQueue(Stack<?> stack, Thread thread) {
            // We allocated a Link so reserve the space
            if (!Head.reserveSpaceForLink(stack.availableSharedCapacity)) {
                return null;
            }
            final WeakOrderQueue queue = new WeakOrderQueue(stack, thread);
            // Done outside of the constructor to ensure WeakOrderQueue.this does not escape the constructor and so
            // may be accessed while its still constructed.
            // 如果线程2创建一个和Stack关联的WeakOrderQueue，Stack的头节点就会指向线程2创建的WeakOrderQueue。如果之后线程3也创建了一个和Stack关联的WeakOrderQueue，Stack的头节点就会指向新创建的线程3的WeakOrderQueue。
            // 然后线程3的WeakOrderQueue再指向线程2的WeakOrderQueue。也就是无论哪个线程创建一个和Stack关联的WeakOrderQueue时，都插入Stack指向的WeakOrderQueue列表的头部
            stack.setHead(queue);

            return queue;
        }

        WeakOrderQueue getNext() {
            return next;
        }

        void setNext(WeakOrderQueue next) {
            assert next != this;
            this.next = next;
        }

        void reclaimAllSpaceAndUnlink() {
            head.reclaimAllSpaceAndUnlink();
            this.next = null;
        }

        void add(DefaultHandle<?> handle) {
            handle.lastRecycledId = id;

            // While we also enforce the recycling ratio one we transfer objects from the WeakOrderQueue to the Stack
            // we better should enforce it as well early. Missing to do so may let the WeakOrderQueue grow very fast
            // without control if the Stack
            if (handleRecycleCount < interval) {
                handleRecycleCount++;
                // Drop the item to prevent recycling to aggressive.
                return;
            }
            handleRecycleCount = 0;

            // 获取当前的WeakOrderQueue指向的最后一个link的指针，也就是尾指针
            Link tail = this.tail;
            int writeIndex;
            // tail.get()表示获取当前link中已经填充元素的个数，如果等于16，说明元素已经填满
            if ((writeIndex = tail.get()) == LINK_CAPACITY) {
            	// 通过reserveSpaceForLink方法判断当前WeakOrderQueue是否还能缓存handle对象，如果不能，则返回
                Link link = head.newLink();
                if (link == null) {
                    // Drop it.
                    return;
                }
                // 如果还能继续缓存，则再创建一个link，并将尾节点指向新创建的link，并且原来尾节点的next指向新创建的link，然后获取当前link的writeIndex，就是写指针
                this.tail = tail = tail.next = link;

                writeIndex = tail.get();
            }
            // tail.get(): 0 // 如果新创建的link中没有元素，writeIndex为0，之后将尾部的link的elements属性，也就是一个handle类型的数组，通过数组下标的方式将第writeIndex的位置赋值为要回收的handle，
            // 然后将handle的Stack属性设置为null，表示当前handle不是通过Stack进行回收的
            tail.elements[writeIndex] = handle;
            handle.stack = null;
            // we lazy set to ensure that setting stack to null appears before we unnull it in the owning thread;
            // this also means we guarantee visibility of an element in the queue if we see the index updated
            // 最后将tail节点的元素个数加1，表示下一次将从writeIndex + 1的位置往里写
            tail.lazySet(writeIndex + 1);
        }

        boolean hasFinalData() {
            return tail.readIndex != tail.get();
        }

        // transfer as many items as we can from this queue to the stack, returning true if any were transferred
        /**剖析之前这里我们回顾图《WeakOrderQueue的数据结构》
         * <br/>WeakOrderQueue是由多个link组成，每个link通过链表的方式进行关联，其中head属性指向第一个link，tail属性指向最后一个link
         * <br/>在每个link中有多个handle，在link中维护了一个读指针readIndex，标记着读取link中handle的位置
         * @param dst
         * @return
         */
        @SuppressWarnings("rawtypes")
        boolean transfer(Stack<?> dst) {
        	// 首先获取头结点link，并判断头结点link是否为空，如果头结点link为空，说明当前WeakOrderQueue并没有link，返回false
            Link head = this.head.link;
            if (head == null) {
                return false;
            }

            // 这里判断读指针是否为16，因为link中元素最大数量就是16，如果读指针为16，说明当前link中的数据都被取走了
            if (head.readIndex == LINK_CAPACITY) {
            	// 表示是否还有下一个link，如果没有下一个link，则说明当前WeakOrderQueue没有元素了，则返回false
                if (head.next == null) {
                    return false;
                }
                head = head.next;
                this.head.relink(head);
            }

            // 拿到head节点的读指针和head中元素的数量，接着计算可以传输元素的大小，如果大小为0，则返回false，见《可以传输元素的大小》
            final int srcStart = head.readIndex;
            int srcEnd = head.get(); // link(extends AtomicInteger)的value
            final int srcSize = srcEnd - srcStart;
            if (srcSize == 0) {
                return false;
            }

            // 接着，拿到当前stack数组已经使用的大小，再加上可以传输的大小表示stack中所需要的容量
            final int dstSize = dst.size;
            final int expectedCapacity = dstSize + srcSize;

            // 如果需要的容量大于当前stack中所维护的数组的大小，则将stack中维护的数组进行扩容，进入if块中
            if (expectedCapacity > dst.elements.length) {
                final int actualCapacity = dst.increaseCapacity(expectedCapacity);
                // actualCapacity - dstSize: 扩容后的大小 - 原Stack的大小，就是最多能往Stack中传输多少元素
                // srcStart + (actualCapacity - dstSize): 表示往Stack中传输的最后一个下标，这里的下标和srcEnd中取一个较小的值，也就是既不能超过Stack的容量，也不能造成当前link中下标越界
                srcEnd = min(srcStart + actualCapacity - dstSize, srcEnd);
            }

            // 表示能不能同link中获取内容，如果不能，则返回false，如果可以，则进入if块中
            if (srcStart != srcEnd) {
            	// 接着拿到当前link的数组elements和stack中的数组elements
                final DefaultHandle[] srcElems = head.elements;
                final DefaultHandle[] dstElems = dst.elements;
                // 初始化stack的下标，表示stack中从这个下标开始添加数据
                int newDstSize = dstSize;
                // 然后通过for循环，通过数组下标的方式不断的将当前link中的数据放入到stack中
                for (int i = srcStart; i < srcEnd; i++) {
                    DefaultHandle<?> element = srcElems[i];
                    // 这里 element.recycleId == 0 表示对象没有被回收过，如果没有被回收过，则赋值为lastRecycledId，我们前面分析过lastRecycledId是WeakOrderQueue中的唯一下标，通过赋值标记element被回收过
					// 然后继续判断 element.recycleId != element.lastRecycledId，这表示该对象被回收过，但是回收的recycleId却不是最后一次回收lastRecycledId，这是一种异常情况，表示一个对象在不同的地方被回收过两次，这种情况则抛出异常
                    if (element.recycleId == 0) {
                        element.recycleId = element.lastRecycledId;
                    } else if (element.recycleId != element.lastRecycledId) {
                        throw new IllegalStateException("recycled already");
                    }
                    // 接着将link的第i个元素设置为null
                    srcElems[i] = null;

                    if (dst.dropHandle(element)) {
                        // Drop the object.
                        continue;
                    }
                    // 表示将handle的stack属性设置到当前stack，相当于被当前线程回收
                    element.stack = dst;
                    // 通过数组的下标的方式将link中的handle赋值到stack的数组中
                    dstElems[newDstSize ++] = element;
                }

                if (srcEnd == LINK_CAPACITY && head.next != null) {
                    // Add capacity back as the Link is GCed.
                    this.head.relink(head.next);
                }

                // 将读指针指向srcEnd，下一次读取可以从srcEnd开始
                head.readIndex = srcEnd;
                // 表示没有向stack传输任何对象，则返回false
                if (dst.size == newDstSize) {
                    return false;
                }
                // 否则更新stack的大小为newDstSize，并返回true
                dst.size = newDstSize;
                return true;
            } else {
                // The destination stack is full already.
                return false;
            }
        }
    }

    private static final class Stack<T> {

        // we keep a queue of per-thread queues, which is appended to once only, each time a new thread other
        // than the stack owner recycles: when we run out of items in our stack we iterate this collection
        // to scavenge those that can be reused. this permits us to incur minimal thread synchronisation whilst
        // still recycling all items.
        /**表示Recycler自身
         *
         */
        final Recycler<T> parent;

        // We store the Thread in a WeakReference as otherwise we may be the only ones that still hold a strong
        // Reference to the Thread itself after it died because DefaultHandle will hold a reference to the Stack.
        //
        // The biggest issue is if we do not use a WeakReference the Thread may not be able to be collected at all if
        // the user will store a reference to the DefaultHandle somewhere and never clear this reference (or not clear
        // it in a timely manner).
        /**表示当前Stack绑定的哪个线程
         *
         */
        final WeakReference<Thread> threadRef;
        /**表示在线程A中创建的对象，在其他线程中缓存的最大个数，即线程A的Stack允许外部线程给其缓存多少个对象
         * 
         */
        final AtomicInteger availableSharedCapacity;
        /**很多时候，一个线程（线程1）创建的对象，有可能会被另一个线程（线程2）释放，而线程2释放的对象不会放在当前线程的Stack中，而是存放在一个叫做WeakOrderQueue的数据结构中，里面也存放着一个个DefaultHandler，WeakOrderQueue会存放线程1创建且在线程2进行释放的对象
         * <br/>所以这个属性的意思就是设置线程2能回收的其他线程对象的最大值。假设maxDelayedQueues设置为2，那么线程2回收了线程1创建的对象，又回收了线程3创建的对象，就不能再回收线程4创建的对象，最多只能回收2个线程创建的对象
         */
        private final int maxDelayedQueues;

        /**表示当前Stack的最大容量，表示Stack最多能盛放多少个元素
         * 
         */
        private final int maxCapacity;
        /**用来控制对象回收的频率，也就是说每次通过Recycler回收对象的时候，不是每次都会进行回收，而是通过该参数控制回收频率
         * 
         */
        private final int interval;
        /**表示Stack中存储的对象，类型为DefaultHandle，可以被外部对象引用，从而实现回收
         * 
         */
        DefaultHandle<?>[] elements;
        int size;
        /**表示当前位置Stack回收了多少次对象（回收了多少次，不代表回收了多少个对象，因为不是每次回收都会被成功的保存在Stack中）
         * 
         */
        private int handleRecycleCount;
        /**cursor代表寻找当前的WeakOrderQueue，prev是cursor的上一个节点，见《cursor, prev》
         * 
         */
        private WeakOrderQueue cursor, prev;
        /**指向最近创建的与Stack关联的WeakOrderQueue，也就是头节点，见《cursor, prev》
         * 
         */
        private volatile WeakOrderQueue head;

        Stack(Recycler<T> parent, Thread thread, int maxCapacity, int maxSharedCapacityFactor, int interval, int maxDelayedQueues) {
            this.parent = parent;
            threadRef = new WeakReference<Thread>(thread);
            this.maxCapacity = maxCapacity;
            availableSharedCapacity = new AtomicInteger(max(maxCapacity / maxSharedCapacityFactor, LINK_CAPACITY));
            elements = new DefaultHandle[min(INITIAL_CAPACITY, maxCapacity)];
            this.interval = interval;
            handleRecycleCount = interval; // Start at interval so the first one will be recycled.
            this.maxDelayedQueues = maxDelayedQueues;
        }

        // Marked as synchronized to ensure this is serialized.
        synchronized void setHead(WeakOrderQueue queue) {
            queue.setNext(head);
            head = queue;
        }

        int increaseCapacity(int expectedCapacity) {
            int newCapacity = elements.length;
            int maxCapacity = this.maxCapacity;
            do {
                newCapacity <<= 1;
            } while (newCapacity < expectedCapacity && newCapacity < maxCapacity);

            newCapacity = min(newCapacity, maxCapacity);
            if (newCapacity != elements.length) {
                elements = Arrays.copyOf(elements, newCapacity);
            }

            return newCapacity;
        }

        @SuppressWarnings({ "unchecked", "rawtypes" })
        DefaultHandle<T> pop() {
            int size = this.size;
            if (size == 0) {
            	// 这里我们重点关注，如果size为空，也就是当前tack为空的情况下，会走到scavenge方法，这个方法，就是从WeakOrderQueue获取对象的方法
                if (!scavenge()) {
                    return null;
                }
                size = this.size;
                if (size <= 0) {
                    // double check, avoid races
                    return null;
                }
            }
            // 如果size大于0，则进行size自减，代表取出一个元素
            size --;
            // 然后通过size的数组下标的方式将handle取出，之后将当前下标设置为null
            DefaultHandle ret = elements[size];
            elements[size] = null;
            // As we already set the element[size] to null we also need to store the updated size before we do
            // any validation. Otherwise we may see a null value when later try to pop again without a new element
            // added before.
            this.size = size;

            // 最后将属性recycleId、lastRecycledId、size进行赋值
            if (ret.lastRecycledId != ret.recycleId) {
                throw new IllegalStateException("recycled multiple times");
            }
            ret.recycleId = 0;
            ret.lastRecycledId = 0;
            return ret;
        }

        private boolean scavenge() {
            // continue an existing scavenge, if any
        	// scavengeSome方法表示已经回收到了对象，则直接返回，如果没有回收到对象，则将prev和cursor两个指针进行重置
            if (scavengeSome()) {
                return true;
            }

            // reset our scavenge cursor
            prev = null;
            cursor = head;
            return false;
        }

        private boolean scavengeSome() {
            WeakOrderQueue prev;
            // 首先拿到cursor指针，cursor指针代表要回收的WeakOrderQueue
            WeakOrderQueue cursor = this.cursor;
            if (cursor == null) {
                prev = null;
                cursor = head;
                // 如果cursor为空，则让其指向头节点，如果头节点也为空，说明当前stack没有与其关联的WeakOrderQueue，则返回false
                if (cursor == null) {
                    return false;
                }
            } else {
                prev = this.prev;
            }

            // 通过一个布尔值success标记回收状态
            boolean success = false;
            // do-while循环的终止条件是：遍历到最后一个节点或者回收到元素
            do {
            	// 表示从当前指针指向的WeakOrderQueue中将元素放入到当前stack中，如果取出成功则将success设置为true并跳出循环
                if (cursor.transfer(this)) {
                    success = true;
                    break;
                }
                // 如果没有获得元素，则会通过next属性拿到下一个WeakOrderQueue
                WeakOrderQueue next = cursor.getNext();
                // cursor.get()就是与当前WeakOrderQueue关联的一个线程，get方法就是获得关联的线程对象，如果这个对象为null说明该线程不存在，则进入if块，也就是一些清理的工作
                if (cursor.get() == null) {
                    // If the thread associated with the queue is gone, unlink it, after
                    // performing a volatile read to confirm there is no data left to collect.
                    // We never unlink the first queue, as we don't want to synchronize on updating the head.
                	// 这里表示当前的WeakOrderQueue中是否还有数据，如果有数据则通过for循环将数据通过transfer方法传输到当前stack中，传输成功的，将success标记为true
                    if (cursor.hasFinalData()) {
                    	// transfer方法是将WeakOrderQueue中一个link中的handle往stack进行传输, 有关link的相关内容, 我们上一小节也进行过分析，所以这里通过for循环将每个link的中的数据传输到stack中
                        for (;;) {
                            if (cursor.transfer(this)) {
                                success = true;
                            } else {
                                break;
                            }
                        }
                    }

                    // 继续往下看，如果pre节点不为空，则通过prev.next = next将cursor节点进行释放，也就是pre的下一个节点指向cursor的下一个节点
                    if (prev != null) {
                        // Ensure we reclaim all space before dropping the WeakOrderQueue to be GC'ed.
                        cursor.reclaimAllSpaceAndUnlink();
                        prev.setNext(next);
                    }
                } else {
                	// 这里表示如果当前线程还在，则将prev赋值为cursor，代表prev后移一个节点
                    prev = cursor;
                }

                // 最后通过cursor = next将cursor后移一位，然后再继续进行循环
                cursor = next;

            } while (cursor != null && !success);

            // 循环结束之后，将stack的prev和cursor属性进行保存
            this.prev = prev;
            this.cursor = cursor;
            return success;
        }

        void push(DefaultHandle<?> item) {
        	// 首先判断当前线程和创建Stack的时候保存的线程是否是同一个线程
            Thread currentThread = Thread.currentThread();
            if (threadRef.get() == currentThread) {
                // 如果是，说明是同线程回收对象，则执行pushNow方法将对象放入Stack中
                pushNow(item);
            } else {
                // The current Thread is not the one that belongs to the Stack
                // (or the Thread that belonged to the Stack was collected already), we need to signal that the push
                // happens later.
                pushLater(item, currentThread);
            }
        }

        private void pushNow(DefaultHandle<?> item) {
        	// 如果是第一次回收，recycleId和lastRecycledId都是0，则不会进入if判断
            if ((item.recycleId | item.lastRecycledId) != 0) {
                throw new IllegalStateException("recycled already");
            }
            // 这里将recycleId和lastRecycledId都赋值为OWN_THREAD_ID，OWN_THREAD_ID在每一个recycle中都是唯一固定的
            item.recycleId = item.lastRecycledId = OWN_THREAD_ID;
            
            // 获取当前的size，如果size超过上限，则直接返回
            int size = this.size;
            if (size >= maxCapacity || dropHandle(item)) {
                // Hit the maximum capacity or should drop - drop the possibly youngest object.
                return;
            }
            if (size == elements.length) {
            	// 如果size大小等于Stack中的数组elements的大小，则将数组elements进行扩容，最后size通过数组下标的方式将当前handle设置到elements的元素中，并将size进行自增
                elements = Arrays.copyOf(elements, min(size << 1, maxCapacity));
            }

            elements[size] = item;
            this.size = size + 1;
        }

        private void pushLater(DefaultHandle<?> item, Thread thread) {
            if (maxDelayedQueues == 0) {
                // 如果maxDelayedQueues为0，表示不支持异线程回收
                return;
            }

            // we don't want to have a ref to the queue as the value in our weak map
            // so we null it out; to ensure there are no races with restoring it later
            // we impose a memory ordering here (no-op on x86)
            // key是Stack，value是WeakOrderQueue，说明不同的Stack对应不同的WeakOrderQueue
            // 比如线程1创建了一个对象，在线程3进行了回收；线程2创建了一个对象，同样也在线程3进行了回收，那么线程3的Map里就保存了两组关系：线程1对应的Stack和WeakOrderQueue，以及线程2对应的Stack和WeakOrderQueue
            Map<Stack<?>, WeakOrderQueue> delayedRecycled = DELAYED_RECYCLED.get();
            // this是当前被回收对象的Stack，也就是创建对象的线程对应的Stack
            WeakOrderQueue queue = delayedRecycled.get(this);
            if (queue == null) {
            	// delayedRecycled.size(): 表示当前线程回收其他创建对象的线程的个数
	        	// maxDelayedQueues: 表示最多能回收的线程个数，超过这个值，就表示当前线程不能再回收其他线程的对象了
	            if (delayedRecycled.size() >= maxDelayedQueues) {
                    // Add a dummy queue so we know we should drop the object
	            	// 标识创建对象的线程的Stack所对应的WeakOrderQueue不可用，DUMMY可以理解为不可用
                    delayedRecycled.put(this, WeakOrderQueue.DUMMY);
                    return;
                }
                // Check if we already reached the maximum number of delayed queues and if we can allocate at all.
                if ((queue = newWeakOrderQueue(thread)) == null) {
                    // drop object
                    return;
                }
                delayedRecycled.put(this, queue);
            } else if (queue == WeakOrderQueue.DUMMY) {
                // drop object
                return;
            }

            queue.add(item);
        }

        /**
         * Allocate a new {@link WeakOrderQueue} or return {@code null} if not possible.
         */
        private WeakOrderQueue newWeakOrderQueue(Thread thread) {
            return WeakOrderQueue.newQueue(this, thread);
        }

        boolean dropHandle(DefaultHandle<?> handle) {
        	// 表示当前对象之前是否没有被回收过，如果是第一次回收，会返回true，然后进入if
            if (!handle.hasBeenRecycled) {
                if (handleRecycleCount < interval) {
                	// 每经过handleRecycleCount次调用回收方法，才真正被回收一次，进入这里代表不被回收
                    handleRecycleCount++;
                    // Drop the object.
                    return true;
                }
                handleRecycleCount = 0;
                handle.hasBeenRecycled = true;
            }
            return false;
        }

        DefaultHandle<T> newHandle() {
            return new DefaultHandle<T>(this);
        }
    }
}
